package com.itzg.vboxfarm.service;

import java.util.Date;
import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.itzg.vboxfarm.bits.Constants;
import com.itzg.vboxfarm.domain.HostMachineMeasure;

@Service
@Transactional
public class HostStorageService {
	private static Logger logger = LoggerFactory
			.getLogger(HostStorageService.class);
	
	@PersistenceContext
	EntityManager em;
	
	@Autowired
	ThreadPoolTaskScheduler scheduler;
	
	private long maxMeasureAge = 60*Constants.MSEC_PER_MINUTE;
	
	@Value("${hostStats.maxMeasureAge:60}")
	public void setMaxMeasureAge(String ageInMinutes) {
		logger.debug("maxMeasureAge got set to {}", ageInMinutes);
		maxMeasureAge = Long.parseLong(ageInMinutes)*Constants.MSEC_PER_MINUTE;
	}
	
	private Runnable purgeRunner = new Runnable() {
		@Override
		public void run() {
			purge();
		}
	};

	public void storeMeasures(List<HostMachineMeasure> measures) {
		for (HostMachineMeasure hostMachineMeasure : measures) {
			em.persist(hostMachineMeasure);
		}
//		scheduler.submit(purgeRunner);
	}

	@SuppressWarnings("unchecked")
	@Transactional(readOnly=true)
	public List<Object[]> getMetricsByTime(long hostId, String metric, Date tsStart) {
		return em.createQuery("SELECT ts, value FROM HostMachineMeasure " +
				" WHERE hostMachine.id = :hostId AND measureName = :metric" +
				"  AND aggType IS NULL" +
				"  AND ts > :tsStart" +
				" ORDER BY ts")
			.setParameter("hostId", hostId)
			.setParameter("metric", metric)
			.setParameter("tsStart", tsStart)
			.getResultList();
	}

	public void purge() {
		int count = em.createQuery("DELETE FROM HostMachineMeasure" +
				" WHERE ts < :youngest")
				.setParameter("youngest", new Date(System.currentTimeMillis()-maxMeasureAge))
				.executeUpdate();
		logger.debug("Purged {} measures", count);
	}
}
